package com.witmore.ftp.web.config;

import com.witmore.ftp.web.service.CustomUserManager;
import com.witmore.ftp.web.listener.FtpServerListener;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.apache.ftpserver.FtpServer;
import org.apache.ftpserver.FtpServerFactory;
import org.apache.ftpserver.ftplet.FtpException;
import org.apache.ftpserver.listener.ListenerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.context.event.ContextRefreshedEvent;
import org.springframework.context.event.EventListener;

import jakarta.annotation.PreDestroy;
import java.io.File;

/**
 * FTP服务器配置类
 */
@Slf4j
@Configuration
@RequiredArgsConstructor
public class FtpServerConfig {

    private final FtpProperties ftpProperties;
    private final CustomUserManager customUserManager;
    private final FtpServerListener ftpServerListener;
    
    @Autowired
    private FtpServer ftpServer;

    @Bean
    public FtpServer ftpServer() throws FtpException {
        FtpServerFactory serverFactory = new FtpServerFactory();

        // 设置用户管理器
        serverFactory.setUserManager(customUserManager);

        // 创建监听器
        ListenerFactory listenerFactory = new ListenerFactory();
        listenerFactory.setPort(ftpProperties.getServer().getPort());
        
        // 配置被动模式端口范围 - 使用Apache FtpServer 1.2.0兼容的API
        String passivePorts = ftpProperties.getServer().getPassivePorts();
        if (passivePorts != null && passivePorts.contains("-")) {
            String[] ports = passivePorts.split("-");
            if (ports.length == 2) {
                try {
                    int startPort = Integer.parseInt(ports[0].trim());
                    int endPort = Integer.parseInt(ports[1].trim());
                    // 被动模式配置 - 使用DataConnectionConfigurationFactory
                    org.apache.ftpserver.DataConnectionConfigurationFactory dataConFactory = 
                        new org.apache.ftpserver.DataConnectionConfigurationFactory();
                    // 设置被动模式外部地址
                    String externalAddress = ftpProperties.getServer().getPassiveExternalAddress();
                    if (externalAddress != null && !externalAddress.trim().isEmpty()) {
                        dataConFactory.setPassiveExternalAddress(externalAddress);
                        log.info("Configured passive external address: {}", externalAddress);
                    } else {
                        log.warn("Passive external address not configured, using server's default IP detection");
                    }
                    dataConFactory.setPassivePorts(startPort + "-" + endPort);
                    listenerFactory.setDataConnectionConfiguration(dataConFactory.createDataConnectionConfiguration());
                    log.info("Configured passive mode ports: {}-{}", startPort, endPort);
                } catch (NumberFormatException e) {
                    log.warn("Invalid passive ports configuration: {}, using default", passivePorts);
                } catch (Exception e) {
                    log.warn("Failed to configure passive mode, using default settings", e);
                }
            }
        }

        // 设置超时时间
        listenerFactory.setIdleTimeout(ftpProperties.getServer().getTimeout() / 1000);

        // 添加监听器
        serverFactory.addListener("default", listenerFactory.createListener());

        // 设置最大连接数 (注释掉，因为API可能不同)
        // serverFactory.setMaxConnections(ftpProperties.getServer().getMaxConnections());

        // 添加FTP事件监听器
        serverFactory.getFtplets().put("ftpServerListener", ftpServerListener);

        // 创建FTP根目录
        createFtpRootDirectory();

        return serverFactory.createServer();
    }

    /**
     * 创建FTP根目录
     */
    private void createFtpRootDirectory() {
        String rootDir = ftpProperties.getServer().getRootDirectory();
        File rootDirectory = new File(rootDir);
        if (!rootDirectory.exists()) {
            boolean created = rootDirectory.mkdirs();
            if (created) {
                log.info("Created FTP root directory: {}", rootDirectory.getAbsolutePath());
            } else {
                log.error("Failed to create FTP root directory: {}", rootDirectory.getAbsolutePath());
            }
        } else {
            log.info("FTP root directory already exists: {}", rootDirectory.getAbsolutePath());
        }
    }

    /**
     * 启动FTP服务器 - 在Spring容器完全初始化后启动
     */
    @EventListener(ContextRefreshedEvent.class)
    public void startFtpServer() {
        try {
            if (ftpServer != null && ftpServer.isStopped()) {
                ftpServer.start();
                log.info("FTP Server started successfully on port {}", ftpProperties.getServer().getPort());
            } else if (ftpServer == null) {
                log.error("FTP Server bean is null, cannot start server");
            } else {
                log.info("FTP Server is already running on port {}", ftpProperties.getServer().getPort());
            }
        } catch (Exception e) {
            log.error("Failed to start FTP Server", e);
            throw new RuntimeException("Failed to start FTP Server", e);
        }
    }

    /**
     * 停止FTP服务器
     */
    @PreDestroy
    public void stopFtpServer() {
        if (ftpServer != null && !ftpServer.isStopped()) {
            ftpServer.stop();
            log.info("FTP Server stopped successfully");
        }
    }
}
